package com.hhs.storage.util;

import com.huaban.analysis.jieba.JiebaSegmenter;

import java.io.Serializable;
import java.text.DateFormat;
import java.text.ParseException;
import java.text.SimpleDateFormat;
import java.time.*;
import java.time.temporal.ChronoUnit;
import java.util.Calendar;
import java.util.Date;
import java.util.GregorianCalendar;
import java.util.List;

/**
 * Class that easily treats date. The format of I/O deals with the following.<br>
 * <p>
 * <pre>
 * [Example February 3, 2001 (15:16:17)]
 * <B>Revision History : </B>
 * <!-- ------------------------------------ START OF Revision History -->
 * 2005/11/07 New making
 * <!-- ------------------------------------ END OF Revision History -->
 * </PRE>
 */
public class DateEasy implements Serializable {

    private static final long serialVersionUID = -4460041062580019056L;

    private SimpleDateFormat dfYYYYsMMsDD = null;

    private SimpleDateFormat dfYYsMMsDD = null;

    private SimpleDateFormat dfYYYYMMDD = null;

    private SimpleDateFormat dfYYMMDD = null;

    private SimpleDateFormat dfYYYYhMMhDD = null;

    private SimpleDateFormat dfYYhMMhDD = null;

    private SimpleDateFormat dfYYYYMMDDHHMMSS = null;

    private SimpleDateFormat dfYYYYsMMsDDsHHcMMcSS = null;

    private SimpleDateFormat dfYYYYhMMhDDhHHcMMcSS = null;

    private SimpleDateFormat dfYYYYsMMsDDsHHcMMcSSpSSS = null;

    private SimpleDateFormat dfHHcMMcSS = null;

    private SimpleDateFormat dfHHcMM = null;

    private SimpleDateFormat dfHHMMSS = null;

    private SimpleDateFormat dfMMsDD = null;
    private SimpleDateFormat dfYYYYMMDDHHMMSSSSS = null;

    private Date date;
    private GregorianCalendar calendar = (GregorianCalendar) Calendar
            .getInstance();

    /**
     * DateEasy with time now internally is generated.
     */
    public DateEasy() {
        date = new Date();
        calendar.setTime(date);
    }

    /**
     * DateEasy with specified time internally is generated.
     *
     * @param source Specified time
     */
    public DateEasy(DateEasy source) {
        this.date = source.date;
        calendar.setTime(this.date);
    }

    /**
     * The specified character string is analyzed and DateEasy is generated. It
     * corresponds to the following character strings.<br>
     * �?2001/02/03<br>
     * �?01/02/03<br>
     * �?20010203<br>
     * �?010203<br>
     * �?2001-02-03<br>
     * �?01-02-03<br>
     * �?20010203151617<br>
     * �?2001/02/03 15:16:17<br>
     * <br>
     * There is "/" in the specified character string. <br>
     * 1. At 11 digits or more ---> [2001/02/03 15:16:17]<br>
     * 2. At 9-10 digit ---> [2001/02/03]<br>
     * 3. At 8 digits or less ---> [01/02/03]<br>
     * <br>
     * There is "-" in the specified character string excluding the
     * above-mentioned.<br>
     * 1. At 9 digits or more ---> [2001-02-03]<br>
     * 2. At 8 digits or less ---> [01-02-03]<br>
     * <br>
     * Excluding the above-mentioned<br>
     * 1. At 9 digits or more ---> [20010203151617]<br>
     * 2. At 7-8 digit ---> [20010203]<br>
     * 3. At 6 digits or less ---> [010203]<br>
     * <br>
     *
     * @param dateStr Date character string
     * @throws ParseException When failing in the analysis
     */
    public DateEasy(String dateStr) throws ParseException {
        int length = dateStr.length();
        if (0 <= dateStr.indexOf('/')) {
            if (19 < length) {
                dfYYYYsMMsDDsHHcMMcSSpSSS = new SimpleDateFormat(
                        "yyyy/MM/dd HH:mm:ss.SSS");
                date = dfYYYYsMMsDDsHHcMMcSSpSSS.parse(dateStr);
            } else if (10 < length) {
                dfYYYYsMMsDDsHHcMMcSS = new SimpleDateFormat(
                        "yyyy/MM/dd HH:mm:ss");
                date = dfYYYYsMMsDDsHHcMMcSS.parse(dateStr);
            } else if (8 < length) {
                dfYYYYsMMsDD = new SimpleDateFormat("yyyy/MM/dd");
                date = dfYYYYsMMsDD.parse(dateStr);
            } else {
                dfYYsMMsDD = new SimpleDateFormat("yy/MM/dd");
                date = dfYYsMMsDD.parse(dateStr);
            }
        } else if (0 <= dateStr.indexOf('-')) {
            if (19 < length) {
                dfYYYYsMMsDDsHHcMMcSSpSSS = new SimpleDateFormat(
                        "yyyy-MM-dd HH:mm:ss.SSS");
                date = dfYYYYsMMsDDsHHcMMcSSpSSS.parse(dateStr);
            } else if (10 < length) {
                dfYYYYsMMsDDsHHcMMcSS = new SimpleDateFormat(
                        "yyyy-MM-dd HH:mm:ss");
                date = dfYYYYsMMsDDsHHcMMcSS.parse(dateStr);
            } else if (8 < length) {
                dfYYYYsMMsDD = new SimpleDateFormat("yyyy-MM-dd");
                date = dfYYYYsMMsDD.parse(dateStr);
            } else {
                dfYYsMMsDD = new SimpleDateFormat("yy-MM-dd");
                date = dfYYsMMsDD.parse(dateStr);
            }
        } else if (0 <= dateStr.indexOf('年')) {
            dateStr = dateStr.replace("年", "-");
            dateStr = dateStr.replace("月", "-");
            dateStr = dateStr.replace("日", "");
            dateStr = StringUtil.safeTrim(dateStr);
            String[] ss = dateStr.split("-");
            ss[1] = StringUtil.addPreZero(NumberUtil.toIntCase(ss[1]), 2);
            ss[2] = StringUtil.addPreZero(NumberUtil.toIntCase(ss[2]), 2);
            dfYYYYMMDDHHMMSS = new SimpleDateFormat("yyyyMMddHHmmss");
            date = dfYYYYMMDDHHMMSS.parse(ss[0] + ss[1] + ss[2] + "000000");
        } else if (8 < length) {
            dfYYYYMMDDHHMMSS = new SimpleDateFormat("yyyyMMddHHmmss");
            date = dfYYYYMMDDHHMMSS.parse(dateStr);
        } else if (6 < length) {
            dfYYYYMMDD = new SimpleDateFormat("yyyyMMdd");
            date = dfYYYYMMDD.parse(dateStr);
        } else {
            dfYYMMDD = new SimpleDateFormat("yyMMdd");
            date = dfYYMMDD.parse(dateStr);
        }

        calendar.setTime(date);
    }

    /**
     * DateEasy with specified Date internally is generated.
     *
     * @param date Date
     */
    public DateEasy(Date date) {
        this.date = date;
        calendar.setTime(date);
    }

    /**
     * DateEasy that shows at the time of the time millisecond from 1970/1/1
     * 00:00:00 GMT is generated.
     *
     * @param time Millisecond from epoch
     */
    public DateEasy(long time) {
        date = new Date(time);
        calendar.setTime(date);
    }
    /**
     * DateEasy that LocalDate construct
     * @param date Millisecond from epoch
     */
    public DateEasy(LocalDate date) {
        long l = date.atStartOfDay().atZone(ZoneId.systemDefault()).toInstant().toEpochMilli() ;
        this.date = new Date(l);
        calendar.setTime(this.date);
    }
    /**
     * DateEasy that LocalDateTime construct
     * @param dateTime Millisecond from epoch
     */
    public DateEasy(LocalDateTime dateTime) {
        long timestamp = dateTime.atZone(ZoneId.systemDefault()).toInstant().toEpochMilli();
        this.date = new Date(timestamp);
        calendar.setTime(this.date);
    }
    /**
     * The character string is acquired by the default format (2001/01/01).
     *
     * @return Formatted character string
     */
    public String toString() {
        return toYYYYsMMsDD();
    }

    /**
     * The character string of 2001/01/01 forms is acquired.
     *
     * @return Formatted character string
     */
    public String toYYYYsMMsDD() {
        if (dfYYYYsMMsDD == null) {
            dfYYYYsMMsDD = new SimpleDateFormat("yyyy/MM/dd");
        }
        return dfYYYYsMMsDD.format(date);
    }

    /**
     * The character string of 01/01/01 forms is acquired.
     *
     * @return Formatted character string
     */
    public String toYYsMMsDD() {
        if (dfYYsMMsDD == null) {
            dfYYsMMsDD = new SimpleDateFormat("yy/MM/dd");
        }
        return dfYYsMMsDD.format(date);
    }

    /**
     * The character string of 20010101 forms is acquired.
     *
     * @return Formatted character string
     */
    public String toYYYYMMDD() {
        if (dfYYYYMMDD == null) {
            dfYYYYMMDD = new SimpleDateFormat("yyyyMMdd");
        }
        return dfYYYYMMDD.format(date);
    }

    /**
     * The character string of 010101 forms is acquired.
     *
     * @return Formatted character string
     */
    public String toYYMMDD() {
        if (dfYYMMDD == null) {
            dfYYMMDD = new SimpleDateFormat("yyMMdd");
        }
        return dfYYMMDD.format(date);
    }

    /**
     * The character string of 2001-01-01 forms is acquired.
     *
     * @return Formatted character string
     */
    public String toYYYYhMMhDD() {
        if (dfYYYYhMMhDD == null) {
            dfYYYYhMMhDD = new SimpleDateFormat("yyyy-MM-dd");
        }
        return dfYYYYhMMhDD.format(date);
    }

    /**
     * The character string of 01-01-01 forms is acquired.
     *
     * @return Formatted character string
     */
    public String toYYhMMhDD() {
        if (dfYYhMMhDD == null) {
            dfYYhMMhDD = new SimpleDateFormat("yy-MM-dd");
        }
        return dfYYhMMhDD.format(date);
    }

    /**
     * The character string of 20010101000000 forms is acquired.
     *
     * @return Formatted character string
     */
    public String toYYYYMMDDHHMMSS() {
        if (dfYYYYMMDDHHMMSS == null) {
            dfYYYYMMDDHHMMSS = new SimpleDateFormat("yyyyMMddHHmmss");
        }
        return dfYYYYMMDDHHMMSS.format(date);
    }

    /**
     * The character string of 2001/01/01 00:00:00 form is acquired.
     *
     * @return Formatted character string
     */
    public String toYYYYsMMsDDsHHcMMcSS() {
        if (dfYYYYsMMsDDsHHcMMcSS == null) {
            dfYYYYsMMsDDsHHcMMcSS = new SimpleDateFormat("yyyy/MM/dd HH:mm:ss");
        }
        return dfYYYYsMMsDDsHHcMMcSS.format(date);
    }

    /**
     * The character string of 2001-01-01 00:00:00 form is acquired.
     *
     * @return Formatted character string
     */
    public String toYYYYhMMhDDhHHcMMcSS() {
        if (dfYYYYhMMhDDhHHcMMcSS == null) {
            dfYYYYhMMhDDhHHcMMcSS = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
        }
        return dfYYYYhMMhDDhHHcMMcSS.format(date);
    }

    /**
     * The character string of 2001年01月01日 form is acquired.
     *
     * @return Formatted character string
     */
    public String toYYYYnnMMnnDD() {
        if (dfYYYYhMMhDDhHHcMMcSS == null) {
            dfYYYYhMMhDDhHHcMMcSS = new SimpleDateFormat("yyyy年MM月dd日");
        }
        return dfYYYYhMMhDDhHHcMMcSS.format(date);
    }

    /**
     * The character string of 2001年01月01日 00:00:00 form is acquired.
     *
     * @return Formatted character string
     */
    public String toYYYYnnMMnnDDnnHHcMMcSS() {
        if (dfYYYYhMMhDDhHHcMMcSS == null) {
            dfYYYYhMMhDDhHHcMMcSS = new SimpleDateFormat("yyyy年MM月dd日 HH:mm:ss");
        }
        return dfYYYYhMMhDDhHHcMMcSS.format(date);
    }

    /**
     * The character string of the form is acquired at 00:00:00.
     *
     * @return Formatted character string
     */
    public String toHHcMMcSS() {
        if (dfHHcMMcSS == null) {
            dfHHcMMcSS = new SimpleDateFormat("HH:mm:ss");
        }
        return dfHHcMMcSS.format(date);
    }

    /**
     * The character string of the form is acquired at 00:00
     *
     * @return Formatted character string
     */
    public String toHHcMM() {
        if (dfHHcMM == null) {
            dfHHcMM = new SimpleDateFormat("HH:mm");
        }
        return dfHHcMM.format(date);
    }

    /**
     * The character string of 000000 forms (second of the season) is acquired.
     *
     * @return Formatted character string
     */
    public String toHHMMSS() {
        if (dfHHMMSS == null) {
            dfHHMMSS = new SimpleDateFormat("HHmmss");
        }
        return dfHHMMSS.format(date);
    }

    /**
     * The character string of 01/01 forms is acquired.
     *
     * @return Formatted character string
     */
    public String toMMsDD() {
        if (dfMMsDD == null) {
            dfMMsDD = new SimpleDateFormat("MM/dd");
        }
        return dfMMsDD.format(date);
    }

    /**
     * DateEasy to LocalDate
     * @return
     */
    public LocalDate toLocalDate(){
        LocalDate ld = LocalDate.parse(this.toYYYYhMMhDD());
        return ld;
    }

    /**
     * DateEasy to LocalDateTime
     * @return
     */
    public LocalDateTime toLocalDateTime(){
        Instant instant = this.date.toInstant();
        // 通过Instant对象获取LocalDateTime对象
        LocalDateTime localDateTime = LocalDateTime.ofInstant(instant, ZoneId.systemDefault());
        return localDateTime;
    }
    /**
     * It is judged whether this date exists since the specified date.
     *
     * @param when Date
     * @return When it is not true when it is early so, this DateEasy object is
     * false from the when object.
     */
    public boolean before(DateEasy when) {
        return date.before(when.date);
    }

    /**
     * It is judged whether this date exists since the specified date.
     *
     * @param when Date
     * @return When it is not true when it is slow so, this DateEasy object is
     * false from the when object.
     */
    public boolean after(DateEasy when) {
        return date.after(when.date);
    }

    /**
     * The year is acquired. The year of the point that this DateEasy shows is
     * returned by four digits.
     *
     * @return year of 4 digits
     */
    public int getYear() {
        return calendar.get(Calendar.YEAR);
    }

    /**
     * It judges at the leap year. It is judged whether year that this DateEasy
     * shows is a leap year.
     *
     * @return For the leap year:true/When it is not so:false
     */
    public boolean isLeapYear() {
        return calendar.isLeapYear(getYear());
    }

    /**
     * It judges on February 29 at the leap year. It judges the day that this
     * DateEasy shows is February 29 in the leap year.
     *
     * @return For an intercalary day:true/When it is not so:false
     */
    public boolean isLeapDay() {
        return calendar.isLeapYear(getYear()) && getMonth() == 2
                && getDate() == 29;
    }

    /**
     * The month is acquired. The month of the point that this DateEasy shows is
     * returned.
     *
     * @return month
     */
    public int getMonth() {
        return calendar.get(Calendar.MONTH) + 1;
    }

    /**
     * The day is acquired. The day of the point that this DateEasy shows of
     * month is returned.
     *
     * @return Day of month
     */
    public int getDate() {
        return calendar.get(Calendar.DATE);
    }

    /**
     * A day of the week is acquired. A day of the week of the point that this
     * DateEasy shows is returned. It is returned by the value of the field of
     * the Calendar class.
     *
     * @return A day of the week
     * @see Calendar#SUNDAY
     * @see Calendar#MONDAY
     * @see Calendar#TUESDAY
     * @see Calendar#WEDNESDAY
     * @see Calendar#THURSDAY
     * @see Calendar#FRIDAY
     * @see Calendar#SATURDAY
     */
    public int getDayOfWeek() {
        int d = calendar.get(Calendar.DAY_OF_WEEK) - 1;
        if (d == 0) {
            return 7;
        }
        return d;
    }

    /**
     * Hour is acquired. The hour of the point that this DateEasy shows is
     * returned by the value of 24 time system.
     *
     * @return Value of 24 time system 0-23
     */
    public int getHour() {
        return calendar.get(Calendar.HOUR_OF_DAY);
    }

    /**
     * The minute is acquired. The minute of the point that this DateEasy shows
     * is returned.
     *
     * @return minute
     */
    public int getMinute() {
        return calendar.get(Calendar.MINUTE);
    }

    /**
     * The second is acquired. The second of the point that this DateEasy shows
     * is returned.
     *
     * @return Second
     */
    public int getSecond() {
        return calendar.get(Calendar.SECOND);
    }

    /**
     * The millisecond is acquired. The millisecond of the point that this
     * DateEasy shows is returned.
     *
     * @return millisecond
     */
    public int getMilliSecond() {
        return calendar.get(Calendar.MILLISECOND);
    }

    /**
     * The year is added. The year is advanced to the extent that specified. The
     * year returns before when the argument is a negative value.
     *
     * @param value Advanced years. Returning years in case of negative value.
     */
    public void addYear(int value) {
        calendar.add(Calendar.YEAR, value);
        date = calendar.getTime();
    }

    /**
     * The month is added. The month is advanced to the extent that specified.
     * The month returns to the month of former when the argument is a negative
     * value.
     *
     * @param value Advanced number of month. Returning number of month in case of
     *              negative value.
     */
    public DateEasy addMonth(int value) {
        calendar.add(Calendar.MONTH, value);
        date = calendar.getTime();
        return this;
    }

    /**
     * The day is added. The day is advanced to the extent that specified. The
     * day returns at the date before when the argument is a negative value. The
     * result will advance after next month when this object shows the end of
     * the month.
     *
     * @param value Advanced days. Returning days in case of negative value.
     */
    public DateEasy addDate(int value) {
        calendar.add(Calendar.DATE, value);
        date = calendar.getTime();
        return this;
    }

    /**
     * The day is added. The day is advanced to the extent that specified. The
     * day returns at the date before when the argument is a negative value. The
     * result will advance after next month when this object shows the end of
     * the month.
     *
     * @param value Advanced days. Returning days in case of negative value.
     */
    public void addSecond(int value) {
        calendar.add(Calendar.SECOND, value);
        date = calendar.getTime();
    }

    /**
     * The Date type data is acquired.
     *
     * @return Date data
     */
    public Date toDate() {
        return date;
    }

    /**
     * 1970/1/1 At 00:00:00 The number of milliseconds from GMT is returned.
     *
     * @return Millisecond
     */
    public long getTime() {
        return date.getTime();
    }

    /**
     * The character string of 2001 forms is acquired.
     *
     * @return Formatted character string
     */
    public String toYYYY() {
        if (dfYYYYMMDD == null) {
            dfYYYYMMDD = new SimpleDateFormat("yyyyMMdd");
        }
        return dfYYYYMMDD.format(date).substring(0, 4);
    }

    /**
     * [01]The character string of the form is acquired.
     *
     * @return Formatted character string
     */
    public String toMM() {
        if (dfYYYYMMDD == null) {
            dfYYYYMMDD = new SimpleDateFormat("yyyyMMdd");
        }
        return dfYYYYMMDD.format(date).substring(4, 6);
    }

    /**
     * [01]The character string of the form is acquired.
     *
     * @return Formatted character string
     */
    public String toDD() {
        if (dfYYYYMMDD == null) {
            dfYYYYMMDD = new SimpleDateFormat("yyyyMMdd");
        }
        return dfYYYYMMDD.format(date).substring(6, 8);
    }

    /**
     * The character string of 20010101000000000 forms is acquired.
     *
     * @return Formatted character string
     */
    public String toYYYYMMDDHHMMSSSSS() {
        if (dfYYYYMMDDHHMMSSSSS == null) {
            dfYYYYMMDDHHMMSSSSS = new SimpleDateFormat("yyyyMMddHHmmssSSS");
        }
        return dfYYYYMMDDHHMMSSSSS.format(date);
    }

    /**
     * The character string of 2001/01/01/ 00:00:00.000 forms is acquired.
     *
     * @return Formatted character string
     */
    public String toYYYYsMMsDDbHHcMMcSSpSSS() {
        if (dfYYYYMMDDHHMMSSSSS == null) {
            dfYYYYMMDDHHMMSSSSS = new SimpleDateFormat(
                    "yyyy/MM/dd HH:mm:ss.SSS");
        }
        return dfYYYYMMDDHHMMSSSSS.format(date);
    }


    /**
     * 两个时间相差距离多少天多少小时多少分多少秒
     * 如果第一个时间比第二个时间大时间差为两者换位
     * @param str1 时间参数 1 格式：1990-01-01 12:00:00
     * @param str2 时间参数 2 格式：2009-01-01 12:00:00
     * @return long[] 返回值为：{天, 时, 分, 秒}
     */
    public static long[] getDistanceTimes(String str1, String str2) {
        DateFormat df = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
        Date one;
        Date two;
        long day = 0;
        long hour = 0;
        long min = 0;
        long sec = 0;
        try {
            one = df.parse(str1);
            two = df.parse(str2);
            long time1 = one.getTime();
            long time2 = two.getTime();
            long diff;
            if (time1 < time2) {
                diff = time2 - time1;
            } else {
                diff = time1 - time2;
            }
            day = diff / (24 * 60 * 60 * 1000);
            hour = (diff / (60 * 60 * 1000) - day * 24);
            min = ((diff / (60 * 1000)) - day * 24 * 60 - hour * 60);
            sec = (diff / 1000 - day * 24 * 60 * 60 - hour * 60 * 60 - min * 60);
        } catch (ParseException e) {
            return new long[]{0, 0, 0, 0};
        }
        long[] times = {day, hour, min, sec};
        return times;
    }

    /**
     * 两个时间相差距离多少天多少小时多少分多少秒
     * 如果第一个时间比第二个时间大全部返回0
     *
     * @param str1 时间参数 1 格式：1990-01-01 12:00:00
     * @param str2 时间参数 2 格式：2009-01-01 12:00:00
     * @return long[] 返回值为：{天, 时, 分, 秒}
     */
    public static long[] getDistanceTimes2(String str1, String str2) {
        DateFormat df = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
        Date one;
        Date two;
        long day = 0;
        long hour = 0;
        long min = 0;
        long sec = 0;
        try {
            one = df.parse(str1);
            two = df.parse(str2);
            long time1 = one.getTime();
            long time2 = two.getTime();
            long diff;
            if (time1 < time2) {
                diff = time2 - time1;
            } else {
                return new long[]{0, 0, 0, 0};
            }
            day = diff / (24 * 60 * 60 * 1000);
            hour = (diff / (60 * 60 * 1000) - day * 24);
            min = ((diff / (60 * 1000)) - day * 24 * 60 - hour * 60);
            sec = (diff / 1000 - day * 24 * 60 * 60 - hour * 60 * 60 - min * 60);
        } catch (ParseException e) {
            return new long[]{0, 0, 0, 0};
        }
        long[] times = {day, hour, min, sec};
        return times;
    }

    /**
     * 得到线性时间秒级
     *
     * @param d 时间参数 1 格式：1990-01-01 12:00:00
     * @return 返回值为秒
     */
    public static int getMSeconds(String d) {
        DateFormat df = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
        Date one;
        long time1 = 0;
        try {
            one = df.parse(d);
            time1 = one.getTime();
        } catch (ParseException e) {
            return 0;
        }
        return (int) (time1 / 1000);
    }

    /**
     * 两个时间相差距离多少毫秒
     */
    public static long getDistanceMSeconds(String str1, String str2) {
        DateFormat df = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
        Date one;
        Date two;
        long diff = 0;
        try {
            one = df.parse(str1);
            two = df.parse(str2);
            long time1 = one.getTime();
            long time2 = two.getTime();
            if (time1 < time2) {
                diff = time2 - time1;
            } else {
                diff = time1 - time2;
            }
        } catch (ParseException e) {
            return 0;
        }
        return diff;
    }

    /**
     * 得时间戳秒级别的
     *
     * @return
     */
    public static int getTimeStamp() {
        return (int) (System.currentTimeMillis() / 1000);
    }

    /**
     * 获取今天指定时间对应的毫秒数
     *
     * @param time "HH:mm:ss"
     * @return
     */
    public static long getTimeMillis(String time) {
        try {
            DateFormat dateFormat = new SimpleDateFormat("yy-MM-dd HH:mm:ss");
            DateFormat dayFormat = new SimpleDateFormat("yy-MM-dd");
            Date curDate = dateFormat.parse(dayFormat.format(new Date()) + " "
                    + time);
            return curDate.getTime();
        } catch (ParseException e) {

        }
        return 0;
    }

    /**
     * 一个时间是不是在两个时间之间 如果开始的时间时间小于结束的时间 在一天之内，
     * 如果开始时间大于结束时间 则跨一天 时间24小时制
     *
     * @param now       格式：HH:mm:ss
     * @param begintime 格式：HH:mm:ss
     * @param endtime   格式：HH:mm:ss
     * @return
     */
    public static boolean betweentimes(String now, String begintime,
                                       String endtime) {
        try {
            new DateEasy("1990-01-01 " + now);
            new DateEasy("1990-01-01 " + begintime);
            new DateEasy("1990-01-01 " + endtime);
        } catch (Exception e) {
            return false;
        }
        now = StringUtil.safeTrim(now);
        begintime = StringUtil.safeTrim(begintime);
        endtime = StringUtil.safeTrim(endtime);
        if (begintime.compareTo(endtime) < 0) {
            if ((now.compareTo(begintime) > 0 || now.compareTo(begintime) == 0)
                    && (now.compareTo(endtime) < 0 || now.compareTo(endtime) == 0)) {
                return true;
            } else {
                return false;
            }
        } else if (begintime.compareTo(endtime) > 0) {
            // 交换
            String t;
            t = begintime;
            begintime = endtime;
            endtime = t;
            if ((now.compareTo(begintime) > 0)
                    && (now.compareTo(endtime)) < 0) {
                return false;
            } else {
                return true;
            }
        } else {
            return true;
        }
    }

    /**
     * 得一个时间的开始时间和结束时间 0是今天的意思
     *
     * @param a,b return String[0] 开始时间，String[1]结束时间
     */
    public static String[] getDateSpan(int a) {
        DateEasy tday = new DateEasy();
        DateEasy begind = new DateEasy(tday);
        DateEasy endd = new DateEasy(tday);
        begind.addDate(a);
        endd.addDate(a + 1);
        String[] rs = new String[]{"", ""};
        rs[0] = begind.toYYYYMMDDHHMMSS().substring(0, 8) + "000000";
        rs[1] = endd.toYYYYMMDDHHMMSS().substring(0, 8) + "000000";
        return rs;
    }

    public static final String[] zodiacArray = {"猴", "鸡", "狗", "猪", "鼠", "牛",
            "虎", "兔", "龙", "蛇", "马", "羊"};

    public static final String[] constellationArray = {"水瓶座", "双鱼座", "牡羊座",
            "金牛座", "双子座", "巨蟹座", "狮子座", "处女座", "天秤座", "天蝎座", "射手座", "魔羯座"};

    public static final int[] constellationEdgeDay = {20, 19, 21, 21, 21, 22,
            23, 23, 23, 23, 22, 22};

    /**
     * 根据日期获取生肖
     *
     * @return
     */
    private static String date2Zodica(Calendar time) {
        return zodiacArray[time.get(Calendar.YEAR) % 12];
    }

    /**
     * 根据日期获取生肖
     *
     * @return
     */
    public static String date2Zodica(String time) {
        Calendar c = Calendar.getInstance();
        SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd");
        Date date;
        try {
            date = sdf.parse(time);
            c.setTime(date);
            String zodica = date2Zodica(c);
            return zodica;
        } catch (ParseException e) {

        }
        return null;
    }

    /**
     * 根据日期获取生肖
     *
     * @return
     */
    public static String date2Zodica(DateEasy time) {
        String timestr = time.toYYYYhMMhDD();
        Calendar c = Calendar.getInstance();
        SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd");
        Date date;
        try {
            date = sdf.parse(timestr);
            c.setTime(date);
            String zodica = date2Zodica(c);
            return zodica;
        } catch (ParseException e) {

        }
        return null;
    }

    /**
     * 根据日期获取星座
     *
     * @param time
     * @return
     */
    public static String date2Constellation(Calendar time) {
        int month = time.get(Calendar.MONTH);
        int day = time.get(Calendar.DAY_OF_MONTH);
        if (day < constellationEdgeDay[month]) {
            month = month - 1;
        }
        if (month >= 0) {
            return constellationArray[month];
        }
        // default to return 魔羯  
        return constellationArray[11];
    }

    /**
     * 根据日期获取星座
     *
     * @param time
     * @return
     */
    public static String date2Constellation(String time) {

        Calendar c = Calendar.getInstance();
        SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd");
        Date date;
        try {
            date = sdf.parse(time);
            c.setTime(date);

            String constellation = date2Constellation(c);
            return constellation;
        } catch (ParseException e) {

        }
        return null;
    }


    /**
     * 获得本周一0点时间
     * @return
     */
    public static DateEasy getTimesWeekMorning() {
        LocalDate today = LocalDate.now();
        DayOfWeek dayOfWeek = today.getDayOfWeek();
        int daysToAdd = DayOfWeek.MONDAY.getValue() - dayOfWeek.getValue();
        LocalDate monday= today.plusDays(daysToAdd);
        return new DateEasy(monday);
    }
    /**
     * 获得指定时间周一0点时间
     * @return
     */
    public static DateEasy getTimesWeekMorning(DateEasy da) {
        LocalDate today = da.toLocalDate();
        DayOfWeek dayOfWeek = today.getDayOfWeek();
        int daysToAdd = DayOfWeek.MONDAY.getValue() - dayOfWeek.getValue();
        LocalDate monday= today.plusDays(daysToAdd);
        return new DateEasy(monday);
    }
    /**
     * 获得本月第一天0点时间
     * @return
     */
    public static DateEasy getTimesMonthMorning() {
        Calendar cal = Calendar.getInstance();
        cal.set(cal.get(Calendar.YEAR), cal.get(Calendar.MONDAY), cal.get(Calendar.DAY_OF_MONTH), 0, 0, 0);
        cal.set(Calendar.DAY_OF_MONTH, cal.getActualMinimum(Calendar.DAY_OF_MONTH));
        return new DateEasy(cal.getTime());
    }
    /**
     * 获得指定月第一天0点时间
     * @return
     */
    public static DateEasy getTimesMonthMorning(DateEasy da) {
        Calendar cal = da.calendar;
        cal.set(cal.get(Calendar.YEAR), cal.get(Calendar.MONDAY), cal.get(Calendar.DAY_OF_MONTH), 0, 0, 0);
        cal.set(Calendar.DAY_OF_MONTH, cal.getActualMinimum(Calendar.DAY_OF_MONTH));
        return new DateEasy(cal.getTime());
    }
    /**
     * 获得本季第一天0点时间
     * @return
     */
    public static DateEasy getTimesJdMorning(DateEasy t) {
        String beginj="";
        int month=Integer.parseInt(t.toMM());
        if(1<=month&&month<=3){
            beginj="01";
        }else if(4<=month&&month<=6){
            beginj="04";
        }else if(7<=month&&month<=9){
            beginj="07";
        }else if(10<=month&&month<=12){
            beginj="10";
        }
        DateEasy da = null;
        try {
            da = new DateEasy(t.toYYYY() + "-" + beginj + "-01");
        } catch (ParseException e) {
            e.printStackTrace();
        }
        return da;
    }

    /**
     * 得到月的第一天
     * @return
     */
    public DateEasy getFirstDayOfMonth(){
        // 获取当前年月
        YearMonth yearMonth = YearMonth.from(this.toLocalDate());
        // 获取本月的最后一个日期
        LocalDate a = yearMonth.atDay(1);
        return new DateEasy(a);
    }
    /**
     * 得到月的最后天
     * @return
     */
    public DateEasy getLastDayOfMonth(){
        // 获取当前年月
        YearMonth yearMonth = YearMonth.from(this.toLocalDate());
        // 获取本月的最后一个日期
        LocalDate a = yearMonth.atEndOfMonth();
        return new DateEasy(a);
    }
    /**
     * 得到最大的天数
     * @throws ParseException
     */
    public int getMaxDate(){
       return this.calendar.getActualMaximum(Calendar.DAY_OF_MONTH);
    }
    public long distancemill(DateEasy da2){
        return this.getTime()-da2.getTime();
    }
    public static void main(String[] args) throws ParseException {
        DateEasy da=new DateEasy();
        DateEasy da2=new DateEasy("20070324");
        System.out.println(da.distancemill(da2));
    }
}
